#include <iostream>
#include <opencv2/opencv.hpp>
using namespace cv;
using namespace std;

/*
	算数运算：
		加法运算：
			void add(InputArray src1, InputArray src2, OutputArray dst,InputArray mask = noArray(), int dtype = -1);
		减法运算：
			void subtract(InputArray src1, InputArray src2, OutputArray dst, InputArray mask = noArray(), int dtype = -1);
		乘法运算：
			void multiply(InputArray src1, InputArray src2, OutputArray dst, double scale = 1, int dtype = -1);
		除法运算:
			void divide(InputArray src1, InputArray src2, OutputArray dst, double scale = 1, int dtype = -1);
		混合运算:
			void addWeighted(InputArray src1, double alpha, InputArray src2, double beta, double gamma, OutputArray dst, int dtype = -1);
				dst= α * img1 + β * img2 + γ = src1 * alpha + src2 * beta + gamma

	位运算：
		按位非：
			void cv::bitwise_not(InputArray src,OutputArray dst,InputArray mask = noArray());
		按位与：
			void cv::bitwise_and(InputArray src1,InputArray src2,OutputArray dst,InputArray mask = noArray());
		按位或
			void cv::bitwise_or(InputArray src1,InputArray src2,OutputArray dst,InputArray mask = noArray());

		按位异或		执行按位异或操作的函数。按位异或操作是指对两个二进制数的对应位进行异或运算，其规则为：如果两个对应位的数相同，则结果为 0；如果两个对应位的数不同，则结果为 1
			void cv::bitwise_xor(InputArray src1,InputArray src2,OutputArray dst,InputArray mask = noArray());
*/

class Image_Operations
{
private:
	Mat img1;
	Mat img2;
	Mat result;
	
public:
	Image_Operations(const string& filename1, const string& filename2)
		:img1(imread(filename1))
		,img2(imread(filename2))
	{
		//记得要将结果图像进行初始化:
		result = Mat::zeros(img2.size(), img2.type());
	}
	Image_Operations()
		:img1(Mat(200, 200, CV_8UC1))
		, img2(Mat(200, 200, CV_8UC1))
	{
		//绘制左上角坐标和绘制矩形的宽度和高度:
		img1(Rect(50, 50, 100, 100)) = Scalar(255);
		img2(Rect(100, 100, 100, 100)) = Scalar(255);

		result = Mat::zeros(img2.size(), img2.type());
	}
	void Show()
	{
		imshow("img1", img1);
		imshow("img2", img2);
		waitKey();
	}

	//算数运算：
	void m_add(const string& type = "add")
	{
		/*
		void add(InputArray src1, InputArray src2, OutputArray dst,InputArray mask = noArray(), int dtype = -1);
		*/

		add(img1, img2, result);
		imshow(type, result);
		waitKey();
	}
	void m_sub(const string& type = "sub")
	{
		/*
		void subtract(InputArray src1, InputArray src2, OutputArray dst, InputArray mask = noArray(), int dtype = -1);
		*/

		subtract(img1, img2, result);
		imshow(type, result);
		waitKey();
	}
	void m_mul(const string& type = "mul")
	{
		/*
		void multiply(InputArray src1, InputArray src2, OutputArray dst, double scale = 1, int dtype = -1);
		*/

		multiply(img1, img2, result);
		imshow(type, result);
		waitKey();
	}
	void m_div(const string& type = "div")
	{
		/*
		void divide(InputArray src1, InputArray src2, OutputArray dst, double scale = 1, int dtype = -1);
		*/

		divide(img1, img2, result);
		imshow(type, result);
		waitKey();
	}
	void m_addWeighted(const string& type = "addWeighted")
	{
		/*
		void addWeighted(InputArray src1, double alpha, InputArray src2, double beta, double gamma, OutputArray dst, int dtype = -1);
				dst= α * img1 + β * img2 + γ = src1 * alpha + src2 * beta + gamma
		*/

		addWeighted(img1, 0.6, img2, 0.4, 0, result);
		imshow(type, result);
		waitKey();
	}

	//位运算：
	void m_bitwise_and(const string& type = "bitwise_and")
	{
		/*
		void cv::bitwise_and(InputArray src1,InputArray src2,OutputArray dst,InputArray mask = noArray());
		*/

		bitwise_and(img1, img2, result);
		imshow(type, result);
		waitKey();
	}
	void m_bitwise_or(const string& type = "bitwise_or")
	{
		/*
		void cv::bitwise_or(InputArray src1,InputArray src2,OutputArray dst,InputArray mask = noArray());
		*/

		bitwise_or(img1, img2, result);
		imshow(type, result);
		waitKey();
	}
	void m_bitwise_not(const string& type = "bitwise_not")
	{
		/*
		void cv::bitwise_not(InputArray src,OutputArray dst,InputArray mask = noArray());
		*/

		bitwise_not(img1, result);
		imshow(type, result);
		waitKey();
	}
	void m_bitwise_xor(const string& type = "bitwise_xor")
	{
		/*
		void cv::bitwise_xor(InputArray src1,InputArray src2,OutputArray dst,InputArray mask = noArray());
		*/
		bitwise_xor(img1, img2, result);
		imshow(type, result);
		waitKey();
	}
};


int main()
{
	//unique_ptr<Image_Operations> imgop(new Image_Operations("mm.jpg", "back.jpg"));
	unique_ptr<Image_Operations> imgop(new Image_Operations());
	imgop->Show();
	imgop->m_add();
	imgop->m_sub();
	imgop->m_mul();
	imgop->m_div();
	imgop->m_addWeighted();

	imgop->m_bitwise_and();
	imgop->m_bitwise_or();
	imgop->m_bitwise_not();
	imgop->m_bitwise_xor();


	return 0;
}
